package controlerLayer;
import guiLayer.extensions.OwnerExistExeption;

import java.util.ArrayList;

import modelLayer.Forest;
import modelLayer.Owner;
import modelLayer.OwnerContainer;
import modelLayer.Tree;


/**
 * The Controller Class for the Owner Objects
 * 
 * @author Nick D. Pedersen 
 * @version 0.1
 */
public class OwnerCtr
{
    private OwnerContainer oCont;

    /**
     * Constructor for objects of class OwnerCtr
     */
    public OwnerCtr(){
        oCont = OwnerContainer.getInstance();
    }

        /**
     * addOwner - Adds an owner by name, address and phoneNumber
         * @throws OwnerExistExeption 
     * @Param String name - The name of the new owner
     * @Param String address - The address of the new owner
     * @Param int phoneNumber - The phone number of the new owner
     */
    public void addOwner(String name, String address, int phoneNumber) throws OwnerExistExeption{
    	try{
    		Owner o = findOwner(name);
    		if(o != null){
    			throw new OwnerExistExeption(name + " already exist!");
    		}
    	}catch(NullPointerException e){
    		oCont.addOwner(new Owner(name, address, phoneNumber));
    	}
    }
    
    /**
     * addOwner - Adds an existing owner
     * @Param Owner o - The existing owner
     */
    public void addOwner(Owner o){
        oCont.addOwner(o);
    }
    
    /**
     * findOwner - Finds an owner by name
     * @Param String name - the name of the owner
     * @Return Owner - The Owner object
     */
    public Owner findOwner(String name) throws NullPointerException{
        Owner o = oCont.findOwner(name);
        if(o != null){
            return o;
        }else{
        	throw new NullPointerException(name + ": Does not exists.");
        }
    }
    
    /**
     * searchOwners - Searches for owner by name
     * @Param String name - name of the owner
     * @Return ArrayList of owners
     */
    public ArrayList<Owner> searchOwners(String name){
    	ArrayList<Owner> owners = oCont.getContainer();
    	ArrayList<Owner> ret = new ArrayList<Owner>();
    	if(owners.size() > 0){
    		for(Owner o : owners){
    			if(o.getName().toLowerCase().contains(name.toLowerCase())){
    				ret.add(o);
    			}
    		}
    	}
    	
    	return ret;
    }

    /**
     * addForestToOwner - Adds a Forest object to an Owner object
     * @Param String ownerName - The name of the Owner object
     * @Param String forestName - The name of the Forest object
     */
    public void addForestToOwner(String ownerName, String forestName){
        ForestCtr fCtr = new ForestCtr();
        Forest f = fCtr.findForest(forestName);
        Owner o = findOwner(ownerName);
        f.setOwner(o);
        o.addForest(f);
    }
    
     /**
     * getOwners - Returns the owners 
     * @Return String - String with the information about the owners
     */
    public String getOwners(){
        String owners = "";
        ArrayList<Owner> oList = oCont.getContainer();
        if(!oList.isEmpty()){
            for(Owner o : oList){
                owners += o.getName() + ", ";
            }
            owners = owners.substring(0, owners.length()-2);
        }else{
            throw new NullPointerException("No Owners to buy from!");
        }
        return owners;
    } 
    
    /**
     * getForests - Returns all Forests owned by the Owner Object
     * @Param String name - The name of the Owner Object
     * @Return String - String with the Forest objects owned by the Owner Object
     */
    public String getForests(String name){
        String forests = "";
        Owner o = oCont.findOwner(name);
        ArrayList<Forest> fList = o.getForests();
        if(!fList.isEmpty()){
            for(Forest f : fList){
                forests += f.getName() + ", ";
            }
            forests = forests.substring(0, forests.length()-2);
        }else{
            throw new NullPointerException("No Forests connected to that Owner");
        }
        return forests;
    }
    
    /**
     * getOwner - Returns a string of information about a given owner
     * @Param String name - name of the owner
     * @Return String - Information of the owner
     */
    public Owner getOwner(String name){
        Owner o = oCont.findOwner(name);
        return o;
    }
    
    /**
     * ownerExists - Checks if the Owner Object exists
     * @Param String - name of the Owner
     * @Return boolean - boolean true/false
     */
    public boolean ownerExist(String name){
        boolean re = false;
        if(oCont.findOwner(name) != null){
            re = true;
        }
        return re;
    }
    
    /**
     * getOwnerInfo - Returns the String value of the given owner.
     * @Return String - String of the value of the owner, and all its objects
     * @Param String name -  The name of the owner.
     */
    public String getOwnerInfo(String name){
        String info = "";
        String nLine = System.getProperty("line.separator");
        Owner o = oCont.findOwner(name);
        ArrayList<Forest> forests = o.getForests();
        info += o + nLine;
        if(!forests.isEmpty()){
            for(Forest f : forests){
                info += "- " + f + nLine;
                ArrayList<Tree> trees = f.getTrees();
                if(!trees.isEmpty()){
                    for(Tree t : trees){
                        info += "-- " + t + nLine;
                    }
                }
            }
        }
        return info;
    }
    
    public ArrayList<Owner> getAllOwners(){
    	return oCont.getContainer();
    }

	public void remove(Owner o) {
		for(Forest f : o.getForests()){
			f.setOwner(null);
		}
		oCont.remove(o);
	}
}
